#ifndef _SERIAL_Multi_BUILD_
#define _SERIAL_Multi_BUILD_
#include <boost/archive/binary_oarchive.hpp>
#include <boost/archive/binary_iarchive.hpp>
#include <boost/serialization/vector.hpp>
//#include "serial_build.h"
#include "../DF_Common/basis_state.h"
#include "../DF_MB/multi_pack.h"
#include "../DF_MB/normal_order.h"
namespace boost {
  namespace serialization {
    //~~~~~~~~~~~~~~~~~~for com_sparse_row.h~~~~~~~~~~~~~~~~~~~~~~~~~//
    template<class Archive>
      void serialize(Archive &ar, SMatrix &a, const unsigned int version){
      ar & a.row_num;
      ar & a.col_num;
      ar & a.tot_num;
      ar & a.row_offsets;
      ar & a.col_indices;
      ar & a.vec_D;
      ar & a.vec_I;
      ar & a.flag_int_double;
    }
    template<class Archive>
      void serialize(Archive &ar, SMatrix_Ch &a, const unsigned int version){
      ar & a.size_ch;
      ar & a.row_num_ch;
      ar & a.col_num_ch;
      ar & a.tot_num_ch;
      ar & a.row_off_ch;
      ar & a.col_ind_ch;
      ar & a.vec_I_ch;
      ar & a.vec_D_ch;
      ar & a.flag_int_double_ch;
    }
    //~~~~~~~~~~~~~~~~~~for coupling_coefff.h~~~~~~~~~~~~~~~~~~~~~~~~~//
    template<class Archive>
      void serialize(Archive &ar, j2m2_state &a, const unsigned int version){
      ar & a.j2a;
      ar & a.m2a;
      ar & a.size;
    }
    template<class Archive>
      void serialize(Archive &ar, jajbJ_state &a, const unsigned int version){
      ar & a.j2a;
      ar & a.j2b;
      ar & a.J2;
      ar & a.index;
    }
    template<class Archive>
      void serialize(Archive &ar, TrK_state &a, const unsigned int version){
      ar & a.k1;
      ar & a.k2;
      ar & a.k3;
    }
    template<class Archive>
      void serialize(Archive &ar, J2M2 &a, const unsigned int version){
      ar & a.vec;
      ar & a.state;
    }
    template<class Archive>
      void serialize(Archive &ar, TrK_cg &a, const unsigned int version){
      ar & a.vec;
      ar & a.state;
      ar & a.exindex3;
      ar & a.inv_exindex3;
    }
    template<class Archive>
      void serialize(Archive &ar, CG_coeff &a, const unsigned int version){
      ar & a.j2a_max;
      ar & a.vec;
      ar & a.J2M2_t;
      ar & a.TrKcg_t;
    }
    template<class Archive>
      void serialize(Archive &ar, JaJbJ &a, const unsigned int version){
      ar & a.vec;
      ar & a.state;
    }
    template<class Archive>
      void serialize(Archive &ar, TrK &a, const unsigned int version){
      ar & a.vec;
      ar & a.state;
      ar & a.exindex2;
      ar & a.exindex3;
    }
    template<class Archive>
      void serialize(Archive &ar, SixJ_coeff &a, const unsigned int version){
      ar & a.j2a_max;
      ar & a.init_info;
      ar & a.vec;
      ar & a.JaJbJ_t;
      ar & a.TrK_t;
    }
    template<class Archive>
      void serialize(Archive &ar, TrK_ninJ &a, const unsigned int version){
      ar & a.vec;
      ar & a.state;
      ar & a.exindex3;
    }
    template<class Archive>
      void serialize(Archive &ar, NinJ_coeff &a, const unsigned int version){
      ar & a.j2a_max;
      ar & a.init_info;
      ar & a.vec;
      ar & a.JaJbJ_t;
      ar & a.TrKninJ_t;
    }
    template<class Archive>
      void serialize(Archive &ar, Binom &a, const unsigned int version){
      ar & a.n_max;
      ar & a.init_info;
      ar & a.vec;
      ar & a.fac2vec;
    }
    //~~~~~~~~~~~~~~~~~~~~for basis_state.h~~~~~~~~~~~~~~~~~~~~~~~~~~//
    template<class Archive>
      void serialize(Archive &ar, channel_Jacobi &chan, const unsigned int version){
      ar & chan.num;
      ar & chan.J_2;
      ar & chan.T_2;
      ar & chan.E_min;
      ar & chan.E_max;
      ar & chan.indexE;
      ar & chan.indexE_beg;
    }
    template<class Archive>
      void serialize(Archive &ar, Channel_DP &chan, const unsigned int version){
      ar & chan.num;
      ar & chan.J_2;
      ar & chan.T_2;
      ar & chan.T_2z;
      ar & chan.E_min;
      ar & chan.E_max;
      ar & chan.indexE;
      ar & chan.indexE_beg;
      ar & chan.E_min_F;
      ar & chan.E_min_I;
      ar & chan.E_max_F;
      ar & chan.E_max_I;
    }
    template<class Archive>
      void serialize(Archive &ar, channel_TP &chan, const unsigned int version){
      ar & chan.num;
      ar & chan.J_2;
      ar & chan.T_2;
      ar & chan.T_2z;
      ar & chan.E_min;
      ar & chan.E_max;
      ar & chan.E_min_F;
      ar & chan.E_min_I;
      ar & chan.E_max_F;
      ar & chan.E_max_I;
      ar & chan.indexE;
      ar & chan.indexE_beg;
    }
    template<class Archive>
      void serialize(Archive &ar, State_SP &SP, const unsigned int version){
      ar & SP.n;
      ar & SP.l;
      ar & SP.E;
      ar & SP.j_2;
      ar & SP.tz_2;
      ar & SP.index;
    }
    template<class Archive>
      void serialize(Archive &ar, State_SPM &SP, const unsigned int version){
      ar & SP.n;
      ar & SP.l;
      ar & SP.E;
      ar & SP.j_2;
      ar & SP.m_2;
      ar & SP.tz_2;  // pn:-1: proton ; 1: neutron tz:0
      ar & SP.index;
    }
    template<class Archive>
      void serialize(Archive &ar, State_DP &DP, const unsigned int version){
      ar & DP.a;
      ar & DP.b;
      ar & DP.J_2;
      ar & DP.T_2;
      ar & DP.T_2z;
      ar & DP.E;
      ar & DP.index;
      ar & DP.I;
      ar & DP.F;
    }
    template<class Archive>
      void serialize(Archive &ar, State_TP &TP, const unsigned int version){
      ar & TP.a;
      ar & TP.b;
      ar & TP.c;
      ar & TP.Jab_2;
      ar & TP.Tab_2;
      ar & TP.Tab_2z;  // pn
      ar & TP.J_2;
      ar & TP.T_2;
      ar & TP.T_2z;
      ar & TP.E;
      ar & TP.Par;
      ar & TP.F;  // 1: exist in final_state
      ar & TP.I;  // 1: exist in initial_state
      //ar & TP.Ecut_Flag; // default=-1; 1: exist
      ar & TP.index;
    }
    template<class Archive>
      void serialize(Archive &ar, State_Conf &SC, const unsigned int version){
        ar & SC.F;
        ar & SC.I;
        ar & SC.E_ex;
      }
    template<class Archive>
      void serialize(Archive &ar, State_TPconf_E &STE, const unsigned int version){
        ar & STE.E_F;
        ar & STE.E_I;
      }
    template<class Archive>
      void serialize(Archive &ar, State_TPM &ST, const unsigned int version){
        ar & ST.a_m;
        ar & ST.b_m;
        ar & ST.c_m;
        ar & ST.Jab_2m;
        ar & ST.Tab_2z;
        ar & ST.J_2m;
        ar & ST.T_2z;
        ar & ST.E;
        ar & ST.index;
      }
    // template<class Archive>
    //   void serialize(Archive &ar, State_Jacobi &SJ, const unsigned int version){
    //   ar & SJ.n12;
    //   ar & SJ.n3;
    //   ar & SJ.l12;
    //   ar & SJ.l3;
    //   ar & SJ.S12_2;
    //   ar & SJ.J12_2;
    //   ar & SJ.j3_2;
    //   ar & SJ.T12_2;
    //   ar & SJ.J_2;
    //   ar & SJ.T_2;
    //   ar & SJ.Par;
    //   ar & SJ.JT_channel;
    //   ar & SJ.E;
    //   ar & SJ.F;  // 1: exist in final_state
    //   ar & SJ.I;  // 1: exist in initial_state
    //   ar & SJ.index;
    //   ar & SJ.flag;
    //   ar & SJ.N_0;
    //   ar & SJ.L_0;
    //   ar & SJ.E_NL;
    //   ar & SJ.J2_NL;
    //   ar & SJ.JTNL_channel;
    //   ar & SJ.index_NL;
    //   ar & SJ.F_NL;
    //   ar & SJ.I_NL;
    // }

    template<class Archive>
      void serialize(Archive &ar, SingleP &SP, const unsigned int version){
      ar & SP.state;
      ar & SP.state_Tz;
      ar & SP.state_TzM;
      ar & SP.index_M2J;
      ar & SP.n_max;
      ar & SP.l_max;
    }
    template<class Archive>
      void serialize(Archive &ar, DoubleP &DP, const unsigned int version){
      ar & DP.state_Tz;
      ar & DP.channel_Tz;
      ar & DP.J2_max;
      ar & DP.J2_max_DP;
      ar & DP.Emax;
      ar & DP.nmax;
      ar & DP.j2max_sp;
      ar & DP.all_size_Tz;
      ar & DP.Emax_Final;
      ar & DP.Emax_Init;
      ar & DP.Emin_Final;
      ar & DP.Emin_Init;
      ar & DP.E_cut_conf;
    }
    template<class Archive>
      void serialize(Archive &ar, TripleP &TP, const unsigned int version){
      ar & TP.state;
      ar & TP.state_Tz;
      ar & TP.state_TzM;
      ar & TP.channel;
      ar & TP.channel_Tz;
      ar & TP.JT2channel;
      ar & TP.TPconf;
      ar & TP.TPconf_Tz;
      ar & TP.TPconf_S;
      ar & TP.TPconf_Tz_S;
      ar & TP.TPconf_k;
      ar & TP.TPconf_k_Tz;
      ar & TP.TPconf_E;
      ar & TP.TPconf_E_Tz;
      ar & TP.TPconf_E_tot;
      ar & TP.E_Jac_conf;
      ar & TP.J2_max;
      ar & TP.J2_max_TP;
      ar & TP.Emax;
      ar & TP.nmax;
      ar & TP.j2max_sp;
      ar & TP.all_size_T;
      ar & TP.all_size_Tz;
      ar & TP.Emax_Final;
      ar & TP.Emax_Init;
      ar & TP.Emin_Final;
      ar & TP.Emin_Init;
      ar & TP.E_cut_conf;
    }
    template<class Archive>
    void serialize(Archive &ar, Multi_Pack &a, const unsigned int version){
      //ar & a.Hbar_Omega;
      ar & a.SP;
      ar & a.TP;
      ar & a.vec_S;
      ar & a.vec_Tz_S;
      ar & a.vec_flag_S;
      ar & a.vec_flag_Tz_S;
      ar & a.LEC_C1;
      ar & a.LEC_C3;
      ar & a.LEC_C4;
      ar & a.LEC_CD;
      ar & a.LEC_CE;
      ar & a.LEC_gA;
      ar & a.hbar_omega;
      ar & a.regulator_pow;
      ar & a.Cut_Lambda;
      ar & a.E_max;
    }
  }
  namespace serialization {
    template<class Archive>
    void serialize(Archive &ar, Norm_Ord_Sec &a, const unsigned int version){
      ar & a.hbar_omega;
      ar & a.vec_U;
      ar & a.vec_UT;
      ar & a.vec_U_flag;
      ar & a.vec_UT_flag;
      ar & a.vec_2V2N;
      ar & a.vec_2V3N;
      ar & a.vec_2V2N_flag;
      ar & a.vec_2V3N_flag;
      //ar & a.vec;
      //ar & a.vec_Tz;
      //ar & a.vec_flag;
      //ar & a.vec_flag_Tz;
    }
  }
}


#endif
